package yxy.game.pm2.module.passbarrier;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.alibaba.fastjson.TypeReference;
import org.joda.time.DateTime;
import org.redisson.api.RList;
import yxy.apple.util.redisson.RedisException;
import yxy.cherry.battle.module.record.result.BattleResult;
import yxy.cherry.game.base.redis.RedisManager;
import yxy.game.pm2.bean.db.newDao.PassbarrierRecordDAO;
import yxy.game.pm2.bean.db.po.PassbarrierRecordPo;
import yxy.game.pm2.bean.module.PlayerModule;

import java.util.ArrayList;
import java.util.List;

public class PassbarrierRecord extends PlayerModule {
    // bean===========================================================================
    private String code;//
    private DateTime date;// 时间
    private ArrayList<String> recordCodes = new ArrayList<>();// 录像码
    private boolean isWin;// 攻方是否胜利
    private RecordPlayerInfo infoA;// 进攻方
    private RecordPlayerInfo infoB;// 防守方
    private BattleResult battleResult;
    private int degree ;
    private int score ;
    private int rank ;

    public int getRank() {
        return rank;
    }

    public void setRank(int rank) {
        this.rank = rank;
    }

    public int getDegree() {
        return degree;
    }

    public void setDegree(int degree) {
        this.degree = degree;
    }

    public int getScore() {
        return score;
    }

    public void setScore(int score) {
        this.score = score;
    }

    public String getCode() {
        return code;
    }

    public void setCode(String code) {
        this.code = code;
    }

    public DateTime getDate() {
        return date;
    }

    public void setDate(DateTime date) {
        this.date = date;
    }

    public ArrayList<String> getRecordCodes() {
        return recordCodes;
    }

    public void setRecordCodes(ArrayList<String> recordCodes) {
        this.recordCodes = recordCodes;
    }

    public boolean isWin() {
        return isWin;
    }

    public void setWin(boolean win) {
        isWin = win;
    }

    public RecordPlayerInfo getInfoA() {
        return infoA;
    }

    public void setInfoA(RecordPlayerInfo infoA) {
        this.infoA = infoA;
    }

    public RecordPlayerInfo getInfoB() {
        return infoB;
    }

    public void setInfoB(RecordPlayerInfo infoB) {
        this.infoB = infoB;
    }

    public BattleResult getBattleResult() {
        return battleResult;
    }

    public void setBattleResult(BattleResult battleResult) {
        this.battleResult = battleResult;
    }

    // func===========================================================================


    // redis==========================================================================

    static public String key(String playerCode) {
        return String.format("PLAYER:%s:MODULE:PASSBARRIERRECORD", playerCode);
    }

    static private RList<PassbarrierRecord> touch(String playerCode) throws RedisException {
        return RedisManager.client(redis()).getList(key(playerCode));
    }

    static public List<PassbarrierRecord> get(String playerCode) {
        try {
            List<PassbarrierRecord> list = touch(playerCode).readAll();
            //缓存没数据从数据库读取并放到redis
            if (list.size() <= 0) {
                List<PassbarrierRecordPo> poList = PassbarrierRecordDAO.getList(playerCode);
                for (int i = 0; i < poList.size(); i++) {
                    PassbarrierRecord passbarrierRecord = toBean(poList.get(i),playerCode);
                    list.add(passbarrierRecord);
                }

                if (list.size() > 0) {
                    //将数据放到缓存
                    touch(playerCode).addAll(list);
                }
            }
            return list;
        } catch (RedisException e) {
            e.printStackTrace();
            return new ArrayList<>();
        }
    }

    static public void add(String playerCode, PassbarrierRecord record) {
        try {
            RList<PassbarrierRecord> rlist = touch(playerCode);
            rlist.add(0, record);
            if (rlist.size() > 10) {
                rlist.trim(0, 9);
            }
        } catch (RedisException e) {
            e.printStackTrace();
        }
    }

    public static void clear(String playerCode) {
        try {
            touch(playerCode).clear();
        } catch (RedisException e) {
            e.printStackTrace();
        }
    }

    //存储到数据库的方法
    public static void saveToDB(String playerCode) {
        try {
            RList<PassbarrierRecord> rList = touch(playerCode);

            if (rList.isExists()) {
                long updateTime = System.currentTimeMillis();
                //存储
                List<PassbarrierRecordPo> passbarrierRecordPoList = new ArrayList<>();
                List<PassbarrierRecord> passbarrierRecordList = rList.readAll();
                for (PassbarrierRecord record : passbarrierRecordList) {
                    PassbarrierRecordPo po = toDbBean(record, playerCode, updateTime);
                    passbarrierRecordPoList.add(po);
                }

                //保存数据库
                PassbarrierRecordDAO.replace(passbarrierRecordPoList);
                //
                PassbarrierRecordDAO.delete(playerCode, updateTime);
            }

        } catch (Exception e) {
            e.printStackTrace();
        }
    }

    //将bean转成po
    private static PassbarrierRecordPo toDbBean(PassbarrierRecord record, String playerCode, long updateTime) {
        PassbarrierRecordPo po = new PassbarrierRecordPo();
        po.setPlayerCode(playerCode);
        po.setCode(record.getCode());
        po.setDate(record.getDate().toDate());
        JSONArray jsonArray = (JSONArray)JSONArray.toJSON(record.getRecordCodes());
        po.setRecordCodes(jsonArray.toString());
        po.setWin(record.isWin());
        JSONObject infoA = (JSONObject)JSONObject.toJSON(record.getInfoA());
        JSONObject infoB = (JSONObject)JSONObject.toJSON(record.getInfoB());
        po.setInfoA(infoA.toString());
        po.setInfoB(infoB.toString());
        po.setDegree(record.getDegree());
        po.setScore(record.getScore());
        po.setRank(record.getRank());
        po.setUpdateTime(updateTime);
        return po;
    }


    //将po转成bean
    private static PassbarrierRecord toBean(PassbarrierRecordPo po,String playerCode) {
        PassbarrierRecord passbarrierRecord = new PassbarrierRecord();
        passbarrierRecord.setPlayerCode(playerCode);
        passbarrierRecord.setPlayerCode(po.getPlayerCode());
        passbarrierRecord.setCode(po.getCode());
        passbarrierRecord.setDate(new DateTime(po.getDate()));

        ArrayList<String> recordCodes = JSON.parseObject(po.getRecordCodes(), new TypeReference<ArrayList<String>>() {
        });
        passbarrierRecord.setRecordCodes(recordCodes);

        passbarrierRecord.setWin(po.isWin());

        RecordPlayerInfo infoA = JSON.parseObject(po.getInfoA(), new TypeReference<RecordPlayerInfo>() {
        });
        passbarrierRecord.setInfoA(infoA);

        RecordPlayerInfo infoB = JSON.parseObject(po.getInfoB(), new TypeReference<RecordPlayerInfo>() {
        });
        passbarrierRecord.setInfoB(infoB);
        passbarrierRecord.setRank(po.getRank());
        passbarrierRecord.setScore(po.getScore());
        passbarrierRecord.setDegree(po.getDegree());
        return passbarrierRecord;
    }

    //移除redis
    public static void removeAllFromRedis(String playerCode) {
        try {
            touchBucket(key(playerCode)).delete();
        } catch (RedisException e) {
            e.printStackTrace();
        }
    }



    /** 录像用玩家信息快照 */
    static public class RecordPlayerInfo {
        private String playerName;
        private int head;
        private int headFrame;

        public String getPlayerName() {
            return playerName;
        }

        public void setPlayerName(String playerName) {
            this.playerName = playerName;
        }

        public int getHead() {
            return head;
        }

        public void setHead(int head) {
            this.head = head;
        }

        public int getHeadFrame() {
            return headFrame;
        }

        public void setHeadFrame(int headFrame) {
            this.headFrame = headFrame;
        }
    }


    // lock==========================================================================

    @Override
    public String lockKey() {
        return String.format("lock:%s", key(getPlayerCode()));
    }

}
